package com.hyphenate.easeui.ui;

import android.app.Activity;
import android.app.ProgressDialog;
import android.content.ClipboardManager;
import android.content.Context;
import android.content.Intent;
import android.content.SharedPreferences;
import android.database.Cursor;
import android.net.Uri;
import android.os.Build;
import android.os.Bundle;
import android.os.Environment;
import android.os.Handler;
import android.os.Message;
import android.provider.MediaStore;
import android.support.v4.widget.SwipeRefreshLayout;
import android.support.v4.widget.SwipeRefreshLayout.OnRefreshListener;
import android.util.Base64;
import android.view.Gravity;
import android.view.LayoutInflater;
import android.view.MotionEvent;
import android.view.View;
import android.view.View.OnClickListener;
import android.view.View.OnTouchListener;
import android.view.ViewGroup;
import android.view.WindowManager;
import android.view.inputmethod.InputMethodManager;
import android.widget.ListView;
import android.widget.Toast;

import com.hyphenate.EMMessageListener;
import com.hyphenate.EMValueCallBack;
import com.hyphenate.chat.EMChatRoom;
import com.hyphenate.chat.EMClient;
import com.hyphenate.chat.EMConversation;
import com.hyphenate.chat.EMGroup;
import com.hyphenate.chat.EMImageMessageBody;
import com.hyphenate.chat.EMMessage;
import com.hyphenate.chat.EMMessage.ChatType;
import com.hyphenate.chat.EMTextMessageBody;
import com.hyphenate.easeui.EaseConstant;
import com.hyphenate.easeui.R;
import com.hyphenate.easeui.controller.EaseUI;
import com.hyphenate.easeui.domain.EaseEmojicon;
import com.hyphenate.easeui.domain.EaseUser;
import com.hyphenate.easeui.model.EaseAtMessageHelper;
import com.hyphenate.easeui.utils.CryptUtil;
import com.hyphenate.easeui.utils.EaseCommonUtils;
import com.hyphenate.easeui.utils.EaseUserUtils;
import com.hyphenate.easeui.utils.FileSaveOnThePhone;
import com.hyphenate.easeui.widget.EaseAlertDialog;
import com.hyphenate.easeui.widget.EaseAlertDialog.AlertDialogUser;
import com.hyphenate.easeui.widget.EaseChatExtendMenu;
import com.hyphenate.easeui.widget.EaseChatInputMenu;
import com.hyphenate.easeui.widget.EaseChatInputMenu.ChatInputMenuListener;
import com.hyphenate.easeui.widget.EaseChatMessageList;
import com.hyphenate.easeui.widget.EaseVoiceRecorderView;
import com.hyphenate.easeui.widget.EaseVoiceRecorderView.EaseVoiceRecorderCallback;
import com.hyphenate.easeui.widget.chatrow.EaseCustomChatRowProvider;
import com.hyphenate.util.EMLog;
import com.hyphenate.util.PathUtil;
import com.zhong.bmob.inter.IChatMessageUpLoadDown;
import com.zhong.bmob.inter.IFileDownLoadDown;
import com.zhong.bmob.inter.IFileUpLoadUserDown;
import com.zhong.bmob.inter.IFindUserDown;
import com.hyphenate.easeui.utils.IOtherFileDownLoadFromBmob;
import com.zhong.bmob.model.ChatMessageBase;
import com.zhong.bmob.model.FileSavePath;
import com.zhong.bmob.model.User;
import com.zhong.bmob.server.ChatMessageUpLoad;
import com.zhong.bmob.server.FileDownLoad;
import com.zhong.bmob.server.FileUpLoad;
import com.zhong.bmob.server.FindUser;
import com.hyphenate.easeui.utils.OtherFileDownLoadFromBmob;

import java.io.File;
import java.util.ArrayList;
import java.util.List;
import java.util.UUID;

import cn.bmob.v3.BmobQuery;
import cn.bmob.v3.datatype.BmobQueryResult;
import cn.bmob.v3.exception.BmobException;
import cn.bmob.v3.listener.SQLQueryListener;

/**
 * you can new an EaseChatFragment to use or you can inherit it to expand.
 * You need call setArguments to pass chatType and userId 
 * <br/>
 * <br/>
 * you can see ChatActivity in demo for your reference
 *
 */
public class EaseChatFragment extends EaseBaseFragment implements EMMessageListener, IFindUserDown, IFileDownLoadDown, IChatMessageUpLoadDown {
    protected static final String TAG = "EaseChatFragment";
    protected static final int REQUEST_CODE_MAP = 1;
    protected static final int REQUEST_CODE_CAMERA = 2;
    protected static final int REQUEST_CODE_LOCAL = 3;
    private MyDialogWarn mDialogWarn;

    /**
     * params to fragment
     */
    protected Bundle fragmentArgs;
    protected int chatType;
    protected String toChatUsername;
    protected EaseChatMessageList messageList;
    protected EaseChatInputMenu inputMenu;

    protected EMConversation conversation;
    
    protected InputMethodManager inputManager;
    protected ClipboardManager clipboard;

    protected Handler handler = new Handler();
    protected File cameraFile;
    protected EaseVoiceRecorderView voiceRecorderView;
    protected SwipeRefreshLayout swipeRefreshLayout;
    protected ListView listView;

    protected boolean isloading;
    protected boolean haveMoreData = true;
    protected int pagesize = 20;
    protected GroupListener groupListener;
    protected ChatRoomListener chatRoomListener;

    protected EMMessage contextMenuMessage;
    
    static final int ITEM_TAKE_PICTURE = 1;
    static final int ITEM_PICTURE = 2;
    static final int ITEM_LOCATION = 3;
    
    protected int[] itemStrings = { R.string.attach_take_pic, R.string.attach_picture, R.string.attach_location };
    protected int[] itemdrawables = { R.drawable.ease_chat_takepic_selector, R.drawable.ease_chat_image_selector,
            R.drawable.ease_chat_location_selector };
    protected int[] itemIds = { ITEM_TAKE_PICTURE, ITEM_PICTURE, ITEM_LOCATION };
    private boolean isMessageListInited;
    protected MyItemClickListener extendMenuItemClickListener;

    private String saveOtherPublicKeyPath;

    private Handler mHandler = new Handler(){
        @Override
        public void handleMessage(Message msg) {
            switch (msg.what) {
                case 110:
                    if (listView.getFirstVisiblePosition() == 0 && !isloading && haveMoreData) {
                        List<EMMessage> messages;
                        try {
                            if (chatType == EaseConstant.CHATTYPE_SINGLE) {
                                messages = conversation.loadMoreMsgFromDB(messageList.getItem(0).getMsgId(),
                                        pagesize);
                            } else {
                                messages = conversation.loadMoreMsgFromDB(messageList.getItem(0).getMsgId(),
                                        pagesize);
                            }
                        } catch (Exception e1) {
                            swipeRefreshLayout.setRefreshing(false);
                            return;
                        }
                        if (messages.size() > 0) {
                            messageList.refreshSeekTo(messages.size() - 1);
                            if (messages.size() != pagesize) {
                                haveMoreData = false;
                            }
                        } else {

                            haveMoreData = false;
                        }

                        isloading = false;

                    } else {
                        Toast.makeText(getActivity(), getResources().getString(R.string.no_more_messages),
                                Toast.LENGTH_SHORT).show();
                    }
                    swipeRefreshLayout.setRefreshing(false);
                    break;
            }
        }
    };

    @Override
    public View onCreateView(LayoutInflater inflater, ViewGroup container, Bundle savedInstanceState) {
        return inflater.inflate(R.layout.ease_fragment_chat, container, false);
    }

    /**
     * 获取对方（可以是单个用户也可以是聊天群）存在Bmob云上的公钥，用于加密发送给对方的信息
     * 如果是聊天群则还要获取该聊天群的私钥
     */
    private void getPublicKeyFromBmob(final String toChatUsername) {
        new Thread(new Runnable() {
            @Override
            public void run() {
                FindUser.query(toChatUsername, EaseChatFragment.this);
            }
        }).start();
    }

    /**
     * 从资源文件中获取指定id所对应的值
     * @param id 资源文件中的id
     * @return 返回指定id所对应的值
     */
    private String getStringFromResource(int id){
        String ret;
        ret = this.getResources().getString(id);
        return ret;
    }

    /**
     * 弹出的Dialog样式
     * @param type type = 1 表示弹出等待Dialog；type = 2、3和4 表示弹出警告Dialog
     */
    public void startWait(final int type) {
        String title = null;
        String content = null;
        if (type == 1) {
            title = getStringFromResource(R.string.Dialog_Warn_Wait_Title);
        }
        mDialogWarn = new MyDialogWarn.Builder(this.getContext(), R.style.MyDialog).
                setTitle(title)
                .setState(type)
                .setContent(content)
                .setCancelable(false)
                .setPositiveButton(new View.OnClickListener() {
                    @Override
                    public void onClick(View view) {
                        if (type == 1) {

                        } else {
                            mDialogWarn.dismiss();
                        }
                    }
                })
                .setNegativeButton(new View.OnClickListener() {
                    @Override
                    public void onClick(View view) {
                        if (type == 1) {
//                            mDialogWarn.dismiss();
                        } else {
                            mDialogWarn.dismiss();
                        }
                    }
                })
                .create();
        mDialogWarn.show();
    }

    /**
     * 取消dialog
     */
    private void stopWait(){
        mDialogWarn.dismiss();
    }

    @Override
    public String getFragmentTitle() {
        return "聊天";
    }

    @Override
    public void onActivityCreated(Bundle savedInstanceState) {

        fragmentArgs = getArguments();
        // check if single chat or group chat
        chatType = fragmentArgs.getInt(EaseConstant.EXTRA_CHAT_TYPE, EaseConstant.CHATTYPE_SINGLE);
        // userId you are chat with or group id
        toChatUsername = fragmentArgs.getString(EaseConstant.EXTRA_USER_ID);
        File file = new File(Environment.getExternalStorageDirectory(), FileSaveOnThePhone.theOtherSave);
        File theOtherUserPubK = new File(file, toChatUsername);
        if (!file.exists() || !theOtherUserPubK.exists()) {
            startWait(1);
            getPublicKeyFromBmob(toChatUsername);
        }else {
            saveOtherPublicKeyPath = theOtherUserPubK.getPath();
        }

        super.onActivityCreated(savedInstanceState);
    }

    /**
     * init view
     */
    protected void initView() {
        // hold to record voice
        //noinspection ConstantConditions
        voiceRecorderView = (EaseVoiceRecorderView) getView().findViewById(R.id.voice_recorder);

        // message list layout
        messageList = (EaseChatMessageList) getView().findViewById(R.id.message_list);
        if(chatType != EaseConstant.CHATTYPE_SINGLE)
            messageList.setShowUserNick(true);
        listView = messageList.getListView();

        extendMenuItemClickListener = new MyItemClickListener();
        inputMenu = (EaseChatInputMenu) getView().findViewById(R.id.input_menu);
        registerExtendMenuItem();
        // init input menu
        inputMenu.init(null);
        inputMenu.setChatInputMenuListener(new ChatInputMenuListener() {

            @Override
            public void onSendMessage(String content) {
                sendTextMessage(content);
            }

            @Override
            public boolean onPressToSpeakBtnTouch(View v, MotionEvent event) {
                return voiceRecorderView.onPressToSpeakBtnTouch(v, event, new EaseVoiceRecorderCallback() {
                    
                    @Override
                    public void onVoiceRecordComplete(String voiceFilePath, int voiceTimeLength) {
                        sendVoiceMessage(voiceFilePath, voiceTimeLength);
                    }
                });
            }

            @Override
            public void onBigExpressionClicked(EaseEmojicon emojicon) {
                sendBigExpressionMessage(emojicon.getName(), emojicon.getIdentityCode());
            }
        });

        swipeRefreshLayout = messageList.getSwipeRefreshLayout();
        swipeRefreshLayout.setColorSchemeResources(R.color.holo_blue_bright, R.color.holo_green_light,
                R.color.holo_orange_light, R.color.holo_red_light);

        inputManager = (InputMethodManager) getActivity().getSystemService(Context.INPUT_METHOD_SERVICE);
        clipboard = (ClipboardManager) getActivity().getSystemService(Context.CLIPBOARD_SERVICE);
        getActivity().getWindow().setSoftInputMode(WindowManager.LayoutParams.SOFT_INPUT_STATE_ALWAYS_HIDDEN);
    }

    protected void setUpView() {
        titleBar.setTitle(toChatUsername);
        if (chatType == EaseConstant.CHATTYPE_SINGLE) {
            // set title
            if(EaseUserUtils.getUserInfo(toChatUsername) != null){
                EaseUser user = EaseUserUtils.getUserInfo(toChatUsername);
                if (user != null) {
                    titleBar.setTitle(user.getNick());
                }
            }
            titleBar.setRightImageResource(R.drawable.ease_mm_title_remove);
        } else {
        	titleBar.setRightImageResource(R.drawable.ease_to_group_details_normal);
            if (chatType == EaseConstant.CHATTYPE_GROUP) {
                //group chat
                EMGroup group = EMClient.getInstance().groupManager().getGroup(toChatUsername);
                if (group != null)
                    titleBar.setTitle(group.getGroupName());
                // listen the event that user moved out group or group is dismissed
                groupListener = new GroupListener();
                EMClient.getInstance().groupManager().addGroupChangeListener(groupListener);
            } else {
                chatRoomListener = new ChatRoomListener();
                EMClient.getInstance().chatroomManager().addChatRoomChangeListener(chatRoomListener);
                onChatRoomViewCreation();
            }

        }
        if (chatType != EaseConstant.CHATTYPE_CHATROOM) {
            onConversationInit();
            onMessageListInit();
        }

        titleBar.setLeftLayoutClickListener(new OnClickListener() {

            @Override
            public void onClick(View v) {
                onBackPressed();
            }
        });
        titleBar.setRightLayoutClickListener(new OnClickListener() {

            @Override
            public void onClick(View v) {
                if (chatType == EaseConstant.CHATTYPE_SINGLE) {
                    emptyHistory();
                } else {
                    toGroupDetails();
                }
            }
        });

        setRefreshLayoutListener();
        
        // show forward message if the message is not null
        String forward_msg_id = getArguments().getString("forward_msg_id");
        if (forward_msg_id != null) {
            forwardMessage(forward_msg_id);
        }
    }
    
    /**
     * register extend menu, item id need > 3 if you override this method and keep exist item
     */
    protected void registerExtendMenuItem(){
        for(int i = 0; i < itemStrings.length; i++){
            inputMenu.registerExtendMenuItem(itemStrings[i], itemdrawables[i], itemIds[i], extendMenuItemClickListener);
        }
    }
    
    
    protected void onConversationInit(){
        conversation = EMClient.getInstance().chatManager().getConversation(toChatUsername, EaseCommonUtils.getConversationType(chatType), true);
        conversation.markAllMessagesAsRead();
        // the number of messages loaded into conversation is getChatOptions().getNumberOfMessagesLoaded
        // you can change this number
        final List<EMMessage> msgs = conversation.getAllMessages();
        int msgCount = msgs != null ? msgs.size() : 0;
        if (msgCount < conversation.getAllMsgCount() && msgCount < pagesize) {
            String msgId = null;
            if (msgs != null && msgs.size() > 0) {
                msgId = msgs.get(0).getMsgId();
            }
            conversation.loadMoreMsgFromDB(msgId, pagesize - msgCount);
        }
        
    }
    
    protected void onMessageListInit(){
        messageList.init(toChatUsername, chatType, chatFragmentHelper != null ? 
                chatFragmentHelper.onSetCustomChatRowProvider() : null);
        setListItemClickListener();
        
        messageList.getListView().setOnTouchListener(new OnTouchListener() {

            @Override
            public boolean onTouch(View v, MotionEvent event) {
                hideKeyboard();
                inputMenu.hideExtendMenuContainer();
                return false;
            }
        });
        
        isMessageListInited = true;
    }
    
    protected void setListItemClickListener() {
        messageList.setItemClickListener(new EaseChatMessageList.MessageListItemClickListener() {
            
            @Override
            public void onUserAvatarClick(String username) {
                if(chatFragmentHelper != null){
                    chatFragmentHelper.onAvatarClick(username);
                }
            }
            
            @Override
            public void onUserAvatarLongClick(String username) {
                if(chatFragmentHelper != null){
                    chatFragmentHelper.onAvatarLongClick(username);
                }
            }
            
            @Override
            public void onResendClick(final EMMessage message) {
                new EaseAlertDialog(getActivity(), R.string.resend, R.string.confirm_resend, null, new AlertDialogUser() {
                    @Override
                    public void onResult(boolean confirmed, Bundle bundle) {
                        if (!confirmed) {
                            return;
                        }
                        resendMessage(message);
                    }
                }, true).show();
            }
            
            @Override
            public void onBubbleLongClick(EMMessage message) {
                contextMenuMessage = message;
                if(chatFragmentHelper != null){
                    chatFragmentHelper.onMessageBubbleLongClick(message);
                }
            }
            
            @Override
            public boolean onBubbleClick(EMMessage message) {
                if(chatFragmentHelper == null){
                    return false;
                }
                return chatFragmentHelper.onMessageBubbleClick(message);
            }

        });
    }

    protected void setRefreshLayoutListener() {
        swipeRefreshLayout.setOnRefreshListener(new OnRefreshListener() {

            @Override
            public void onRefresh() {
                new Handler().postDelayed(new Runnable() {

                    @Override
                    public void run() {
                        //TODO:从服务器的数据库中获取更早的聊天信息
                        List<EMMessage> messagesAll = conversation.getAllMessages();
                        EMMessage message = null;
                        if (messagesAll.size() > 0){
                            message = messagesAll.get(0);
                        }
                        long time = 0L;
                        String to;
                        String from;
                        if (message != null){
                            time = message.getMsgTime(); //能够从本地存储的聊天信息中获取到的最早的一条聊天信息的时间
                            from = message.getFrom();
                            to = message.getTo();
                        }else {
                            SharedPreferences other = getActivity().getSharedPreferences("TalkWithOther", Context.MODE_PRIVATE);
                            from = other.getString("OtherId", "");
                            to = EMClient.getInstance().getCurrentUser();
                        }
                        String sql;
                        if (time == 0L){
                            sql = "select * from ChatMessageBase where to in (? , ?) and from in (?, ?)";
                        }else {
                            sql = "select * from ChatMessageBase where to in (? , ?) and from in (?, ?) and time < ?";
                        }
                        BmobQuery<ChatMessageBase> query = new BmobQuery<>();
                        query.setSQL(sql);
                        query.setPreparedParams(new Object[]{from, to, from, to, time});
                        query.doSQLQuery(new SQLQueryListener<ChatMessageBase>() {
                            @Override
                            public void done(BmobQueryResult<ChatMessageBase> list, BmobException e) {
                                if (e == null){
                                    List<EMMessage> messages = new ArrayList<>();
                                    List<ChatMessageBase> results = list.getResults();
                                    if (results != null && results.size() > 0) {
                                        for (ChatMessageBase base : results) {
                                            String baseTo = base.getTo();
                                            String baseFrom = base.getFrom();
                                            long baseTime = base.getTime();
                                            String id = base.getId();
                                            int type = base.getChatType();
                                            switch (base.getTheType()) {
                                                case 0:
                                                    EMMessage sendTxtMessage = EMMessage.createTxtSendMessage(base.getContent(), baseTo);
                                                    sendTxtMessage.setFrom(baseFrom);
                                                    sendTxtMessage.setTo(baseTo);
                                                    sendTxtMessage.setMsgId(id);
                                                    sendTxtMessage.setMsgTime(baseTime);
                                                    sendTxtMessage.setAcked(true);
                                                    sendTxtMessage.setDelivered(true);
                                                    sendTxtMessage.setStatus(EMMessage.Status.SUCCESS);
                                                    if (EMClient.getInstance().getCurrentUser().equals(baseTo)){
                                                        sendTxtMessage.setDirection(EMMessage.Direct.RECEIVE);
                                                    }else{
                                                        sendTxtMessage.setDirection(EMMessage.Direct.SEND);
                                                    }
                                                    if (type == 0){
                                                        sendTxtMessage.setChatType(ChatType.Chat);
                                                    }else if (type == 1){
                                                        sendTxtMessage.setChatType(ChatType.GroupChat);
                                                    }
                                                    messages.add(sendTxtMessage);
                                                    break;
                                                case 1:
                                                    File file = new File(Environment.getExternalStorageDirectory(), FileSavePath.theChatHistory);
                                                    File imgFile = new File(file, base.getId() + ".jpg");
                                                    if (!imgFile.exists()){
                                                        OtherFileDownLoadFromBmob.doOtherFileDownLoad(messages, id, 1, base.getFilePath(), new IOtherFileDownLoadFromBmob() {
                                                            @Override
                                                            public void OtherFileDownLoadSuccess(List<EMMessage> messages, String s, int type, ChatMessageBase base) {
                                                                EMMessage sendImgMessage = EMMessage.createImageSendMessage(s, false, base.getTo());
                                                                sendImgMessage.setFrom(base.getFrom());
                                                                sendImgMessage.setTo(base.getTo());
                                                                sendImgMessage.setMsgId(base.getId());
                                                                sendImgMessage.setMsgTime(base.getTime());
                                                                sendImgMessage.setAcked(true);
                                                                sendImgMessage.setDelivered(true);
                                                                sendImgMessage.setStatus(EMMessage.Status.SUCCESS);
                                                                if (EMClient.getInstance().getCurrentUser().equals(base.getTo())) {
                                                                    sendImgMessage.setDirection(EMMessage.Direct.RECEIVE);
                                                                } else {
                                                                    sendImgMessage.setDirection(EMMessage.Direct.SEND);
                                                                }
                                                                if (base.getChatType() == 0) {
                                                                    sendImgMessage.setChatType(ChatType.Chat);
                                                                } else if (base.getChatType() == 1) {
                                                                    sendImgMessage.setChatType(ChatType.GroupChat);
                                                                }
                                                                messages.add(sendImgMessage);
                                                            }

                                                            @Override
                                                            public void OtherFileDownLoadFail(BmobException e) {

                                                            }
                                                        }, base);
                                                    }else {
                                                        EMMessage sendImgMessage = EMMessage.createImageSendMessage(imgFile.getPath(), false, base.getTo());
                                                        sendImgMessage.setFrom(base.getFrom());
                                                        sendImgMessage.setTo(base.getTo());
                                                        sendImgMessage.setMsgId(base.getId());
                                                        sendImgMessage.setMsgTime(base.getTime());
                                                        sendImgMessage.setAcked(true);
                                                        sendImgMessage.setDelivered(true);
                                                        sendImgMessage.setStatus(EMMessage.Status.SUCCESS);
                                                        if (EMClient.getInstance().getCurrentUser().equals(base.getTo())) {
                                                            sendImgMessage.setDirection(EMMessage.Direct.RECEIVE);
                                                        } else {
                                                            sendImgMessage.setDirection(EMMessage.Direct.SEND);
                                                        }
                                                        if (base.getChatType() == 0) {
                                                            sendImgMessage.setChatType(ChatType.Chat);
                                                        } else if (base.getChatType() == 1) {
                                                            sendImgMessage.setChatType(ChatType.GroupChat);
                                                        }
                                                        messages.add(sendImgMessage);
                                                    }
                                                    break;
                                                case 2:
                                                    File fileAll = new File(Environment.getExternalStorageDirectory(), FileSavePath.theChatHistory);
                                                    File voiceFile = new File(fileAll, base.getId() + ".amr");
                                                    if (!voiceFile.exists()) {
                                                        OtherFileDownLoadFromBmob.doOtherFileDownLoad(messages, id, 2, base.getFilePath(), new IOtherFileDownLoadFromBmob() {
                                                            @Override
                                                            public void OtherFileDownLoadSuccess(List<EMMessage> messages, String s, int type, ChatMessageBase base) {
                                                                EMMessage sendVoiceMessage = EMMessage.createVoiceSendMessage(s, base.getTimeLength(), base.getTo());
                                                                sendVoiceMessage.setFrom(base.getFrom());
                                                                sendVoiceMessage.setTo(base.getTo());
                                                                sendVoiceMessage.setMsgId(base.getId());
                                                                sendVoiceMessage.setMsgTime(base.getTime());
                                                                sendVoiceMessage.setAcked(true);
                                                                sendVoiceMessage.setDelivered(true);
                                                                sendVoiceMessage.setStatus(EMMessage.Status.SUCCESS);
                                                                if (EMClient.getInstance().getCurrentUser().equals(base.getTo())){
                                                                    sendVoiceMessage.setDirection(EMMessage.Direct.RECEIVE);
                                                                }else{
                                                                    sendVoiceMessage.setDirection(EMMessage.Direct.SEND);
                                                                }
                                                                if (base.getChatType() == 0){
                                                                    sendVoiceMessage.setChatType(ChatType.Chat);
                                                                }else if (base.getChatType() == 1){
                                                                    sendVoiceMessage.setChatType(ChatType.GroupChat);
                                                                }
                                                                messages.add(sendVoiceMessage);
                                                            }

                                                            @Override
                                                            public void OtherFileDownLoadFail(BmobException e) {

                                                            }
                                                        }, base);
                                                    }else {
                                                        EMMessage sendVoiceMessage = EMMessage.createVoiceSendMessage(voiceFile.getPath(), base.getTimeLength(), base.getTo());
                                                        sendVoiceMessage.setFrom(base.getFrom());
                                                        sendVoiceMessage.setTo(base.getTo());
                                                        sendVoiceMessage.setMsgId(base.getId());
                                                        sendVoiceMessage.setMsgTime(base.getTime());
                                                        sendVoiceMessage.setAcked(true);
                                                        sendVoiceMessage.setDelivered(true);
                                                        sendVoiceMessage.setStatus(EMMessage.Status.SUCCESS);
                                                        if (EMClient.getInstance().getCurrentUser().equals(base.getTo())){
                                                            sendVoiceMessage.setDirection(EMMessage.Direct.RECEIVE);
                                                        }else{
                                                            sendVoiceMessage.setDirection(EMMessage.Direct.SEND);
                                                        }
                                                        if (base.getChatType() == 0){
                                                            sendVoiceMessage.setChatType(ChatType.Chat);
                                                        }else if (base.getChatType() == 1){
                                                            sendVoiceMessage.setChatType(ChatType.GroupChat);
                                                        }
                                                        messages.add(sendVoiceMessage);
                                                    }
                                                    break;
                                                case 3:
                                                    EMMessage sendLocationMessage = EMMessage.createLocationSendMessage(base.getLatitude(), base.getLongitude(), base.getLocationAddress(), baseTo);
                                                    sendLocationMessage.setFrom(baseFrom);
                                                    sendLocationMessage.setTo(baseTo);
                                                    sendLocationMessage.setMsgId(id);
                                                    sendLocationMessage.setMsgTime(baseTime);
                                                    sendLocationMessage.setAcked(true);
                                                    sendLocationMessage.setDelivered(true);
                                                    sendLocationMessage.setStatus(EMMessage.Status.SUCCESS);
                                                    if (EMClient.getInstance().getCurrentUser().equals(baseTo)){
                                                        sendLocationMessage.setDirection(EMMessage.Direct.RECEIVE);
                                                    }else{
                                                        sendLocationMessage.setDirection(EMMessage.Direct.SEND);
                                                    }
                                                    if (type == 0){
                                                        sendLocationMessage.setChatType(ChatType.Chat);
                                                    }else if (type == 1){
                                                        sendLocationMessage.setChatType(ChatType.GroupChat);
                                                    }
                                                    messages.add(sendLocationMessage);
                                                    break;
                                                default:
                                                    break;
                                            }
                                        }
                                        EMClient.getInstance().chatManager().importMessages(messages);
                                    }
                                    mHandler.sendEmptyMessage(110);
                                }else {

                                }
                            }
                        });
                    }
                }, 600);
            }
        });
    }

    @Override
    public void onActivityResult(int requestCode, int resultCode, Intent data) {
        super.onActivityResult(requestCode, resultCode, data);
        if (resultCode == Activity.RESULT_OK) { 
            if (requestCode == REQUEST_CODE_CAMERA) { // capture new image
                if (cameraFile != null && cameraFile.exists())
                    sendImageMessage(cameraFile.getAbsolutePath());
            } else if (requestCode == REQUEST_CODE_LOCAL) { // send local image
                if (data != null) {
                    Uri selectedImage = data.getData();
                    if (selectedImage != null) {
                        sendPicByUri(selectedImage);
                    }
                }
            } else if (requestCode == REQUEST_CODE_MAP) { // location
                double latitude = data.getDoubleExtra("latitude", 0);
                double longitude = data.getDoubleExtra("longitude", 0);
                String locationAddress = data.getStringExtra("address");
                if (locationAddress != null && !locationAddress.equals("")) {
                    sendLocationMessage(latitude, longitude, locationAddress);
                } else {
                    Toast.makeText(getActivity(), R.string.unable_to_get_loaction, Toast.LENGTH_SHORT).show();
                }
                
            }
        }
    }


    @Override
    public void onResume() {
        super.onResume();
        if(isMessageListInited)
            messageList.refresh();
        EaseUI.getInstance().pushActivity(getActivity());
        // register the event listener when enter the foreground
        EMClient.getInstance().chatManager().addMessageListener(this);
        
        if(chatType == EaseConstant.CHATTYPE_GROUP){
            EaseAtMessageHelper.get().removeAtMeGroup(toChatUsername);
        }
    }
    
    @Override
    public void onStop() {
        super.onStop();
        // unregister this event listener when this activity enters the
        // background
        EMClient.getInstance().chatManager().removeMessageListener(this);

        // remove activity from foreground activity list
        EaseUI.getInstance().popActivity(getActivity());
    }

    @Override
    public void onDestroy() {
        super.onDestroy();

        if (groupListener != null) {
            EMClient.getInstance().groupManager().removeGroupChangeListener(groupListener);
        }

        if (chatRoomListener != null) {
            EMClient.getInstance().chatroomManager().removeChatRoomListener(chatRoomListener);
        }

        if(chatType == EaseConstant.CHATTYPE_CHATROOM){
            EMClient.getInstance().chatroomManager().leaveChatRoom(toChatUsername);
        }
    }

    public void onBackPressed() {
        if (inputMenu.onBackPressed()) {
            getActivity().finish();
            if(chatType == EaseConstant.CHATTYPE_GROUP){
                EaseAtMessageHelper.get().removeAtMeGroup(toChatUsername);
                EaseAtMessageHelper.get().cleanToAtUserList();
            }
            if (chatType == EaseConstant.CHATTYPE_CHATROOM) {
            	EMClient.getInstance().chatroomManager().leaveChatRoom(toChatUsername);
            }
        }
    }

    protected void onChatRoomViewCreation() {
        final ProgressDialog pd = ProgressDialog.show(getActivity(), "", "Joining......");
        EMClient.getInstance().chatroomManager().joinChatRoom(toChatUsername, new EMValueCallBack<EMChatRoom>() {

            @Override
            public void onSuccess(final EMChatRoom value) {
                getActivity().runOnUiThread(new Runnable() {
                    @Override
                    public void run() {
                        if(getActivity().isFinishing() || !toChatUsername.equals(value.getId()))
                            return;
                        pd.dismiss();
                        EMChatRoom room = EMClient.getInstance().chatroomManager().getChatRoom(toChatUsername);
                        if (room != null) {
                            titleBar.setTitle(room.getName());
                            EMLog.d(TAG, "join room success : " + room.getName());
                        } else {
                            titleBar.setTitle(toChatUsername);
                        }
                        addChatRoomChangeListenr();
                        onConversationInit();
                        onMessageListInit();
                    }
                });
            }

            @Override
            public void onError(final int error, String errorMsg) {
                // TODO Auto-generated method stub
                EMLog.d(TAG, "join room failure : " + error);
                getActivity().runOnUiThread(new Runnable() {
                    @Override
                    public void run() {
                        pd.dismiss();
                    }
                });
                getActivity().finish();
            }
        });
    }

    protected void addChatRoomChangeListenr() {
        /*
        chatRoomChangeListener = new EMChatRoomChangeListener() {

            @Override
            public void onChatRoomDestroyed(String roomId, String roomName) {
                if (roomId.equals(toChatUsername)) {
                    showChatroomToast(" room : " + roomId + " with room name : " + roomName + " was destroyed");
                    getActivity().finish();
                }
            }

            @Override
            public void onMemberJoined(String roomId, String participant) {
                showChatroomToast("member : " + participant + " join the room : " + roomId);
            }

            @Override
            public void onMemberExited(String roomId, String roomName, String participant) {
                showChatroomToast("member : " + participant + " leave the room : " + roomId + " room name : " + roomName);
            }

            @Override
            public void onRemovedFromChatRoom(String roomId, String roomName, String participant) {
                if (roomId.equals(toChatUsername)) {
                    String curUser = EMClient.getInstance().getCurrentUser();
                    if (curUser.equals(participant)) {
                    	EMClient.getInstance().chatroomManager().leaveChatRoom(toChatUsername);
                        getActivity().finish();
                    }else{
                        showChatroomToast("member : " + participant + " was kicked from the room : " + roomId + " room name : " + roomName);
                    }
                }
            }


            // ============================= group_reform new add api begin
            @Override
            public void onMuteListAdded(String chatRoomId, Map<String, Long> mutes) {}

            @Override
            public void onMuteListRemoved(String chatRoomId, List<String> mutes) {}

            @Override
            public void onAdminAdded(String chatRoomId, String admin) {}

            @Override
            public void onAdminRemoved(String chatRoomId, String admin) {}

            @Override
            public void onOwnerChanged(String chatRoomId, String newOwner, String oldOwner) {}

            // ============================= group_reform new add api end

        };
        
        EMClient.getInstance().chatroomManager().addChatRoomChangeListener(chatRoomChangeListener);
        */
    }
    
    protected void showChatroomToast(final String toastContent){
        getActivity().runOnUiThread(new Runnable() {
            public void run() {
                Toast.makeText(getActivity(), toastContent, Toast.LENGTH_SHORT).show();
            }
        });
    }

    // implement methods in EMMessageListener
    @Override
    public void onMessageReceived(List<EMMessage> messages) {
        for (EMMessage message : messages) {
            String username = null;
            // group message
            if (message.getChatType() == ChatType.GroupChat || message.getChatType() == ChatType.ChatRoom) {
                username = message.getTo();
            } else {
                // single chat message
                username = message.getFrom();
            }

            // if the message is for current conversation
            if (username.equals(toChatUsername) || message.getTo().equals(toChatUsername)) {
                messageList.refreshSelectLast();
                EaseUI.getInstance().getNotifier().vibrateAndPlayTone(message);
                conversation.markMessageAsRead(message.getMsgId());
            } else {
                EaseUI.getInstance().getNotifier().onNewMsg(message);
            }
        }
    }

    @Override
    public void onCmdMessageReceived(List<EMMessage> messages) {

    }

    @Override
    public void onMessageRead(List<EMMessage> messages) {
        if(isMessageListInited) {
            messageList.refresh();
        }
    }

    @Override
    public void onMessageDelivered(List<EMMessage> messages) {
        if(isMessageListInited) {
            messageList.refresh();
        }
    }

    @Override
    public void onMessageChanged(EMMessage emMessage, Object change) {
        if(isMessageListInited) {
            messageList.refresh();
        }
    }

    @Override
    public void findSuccess(User user) {
        FileDownLoad.doFileDownLoad(user, EaseChatFragment.this);
    }

    @Override
    public void findFail(BmobException e) {
        stopWait();
    }

    @Override
    public void fileDownSuccess(String savePath) {
        saveOtherPublicKeyPath = savePath;
        stopWait();
    }

    @Override
    public void fileDownFail(BmobException e) {

    }

    @Override
    public void chatMessageUpLoadSuccess(String objectId) {

    }

    @Override
    public void chatMessageUpLoadFail(BmobException e) {

    }

//    @Override
//    public void OtherFileDownLoadSuccess(List<EMMessage> messages, String s, int type, ChatMessageBase base) {
//        switch (type) {
//            case 1:
//                EMMessage sendImgMessage = EMMessage.createImageSendMessage(s, false, base.getTo());
//                sendImgMessage.setFrom(base.getFrom());
//                sendImgMessage.setTo(base.getTo());
//                sendImgMessage.setMsgId(base.getId());
//                sendImgMessage.setMsgTime(base.getTime());
//                sendImgMessage.setAcked(true);
//                sendImgMessage.setDelivered(true);
//                sendImgMessage.setStatus(EMMessage.Status.SUCCESS);
//                if (EMClient.getInstance().getCurrentUser().equals(base.getTo())) {
//                    sendImgMessage.setDirection(EMMessage.Direct.RECEIVE);
//                } else {
//                    sendImgMessage.setDirection(EMMessage.Direct.SEND);
//                }
//                if (base.getChatType() == 0) {
//                    sendImgMessage.setChatType(ChatType.Chat);
//                } else if (base.getChatType() == 1) {
//                    sendImgMessage.setChatType(ChatType.GroupChat);
//                }
//                messages.add(sendImgMessage);
//                break;
//            case 2:
//                EMMessage sendVoiceMessage = EMMessage.createVoiceSendMessage(s, base.getTimeLength(), base.getTo());
//                sendVoiceMessage.setFrom(base.getFrom());
//                sendVoiceMessage.setTo(base.getTo());
//                sendVoiceMessage.setMsgId(base.getId());
//                sendVoiceMessage.setMsgTime(base.getTime());
//                sendVoiceMessage.setAcked(true);
//                sendVoiceMessage.setDelivered(true);
//                sendVoiceMessage.setStatus(EMMessage.Status.SUCCESS);
//                if (EMClient.getInstance().getCurrentUser().equals(base.getTo())){
//                    sendVoiceMessage.setDirection(EMMessage.Direct.RECEIVE);
//                }else{
//                    sendVoiceMessage.setDirection(EMMessage.Direct.SEND);
//                }
//                if (base.getChatType() == 0){
//                    sendVoiceMessage.setChatType(ChatType.Chat);
//                }else if (base.getChatType() == 1){
//                    sendVoiceMessage.setChatType(ChatType.GroupChat);
//                }
//                messages.add(sendVoiceMessage);
//                break;
//            default:
//                break;
//        }
//    }

//    @Override
//    public void OtherFileDownLoadFail(BmobException e) {
//
//    }


    /**
     * handle the click event for extend menu
     *
     */
    class MyItemClickListener implements EaseChatExtendMenu.EaseChatExtendMenuItemClickListener{

        @Override
        public void onClick(int itemId, View view) {
            if(chatFragmentHelper != null){
                if(chatFragmentHelper.onExtendMenuItemClick(itemId, view)){
                    return;
                }
            }
            switch (itemId) {
            case ITEM_TAKE_PICTURE:
                selectPicFromCamera();
                break;
            case ITEM_PICTURE:
                selectPicFromLocal();
                break;
            case ITEM_LOCATION:
                startActivityForResult(new Intent(getActivity(), EaseBaiduMapActivity.class), REQUEST_CODE_MAP);
                break;

            default:
                break;
            }
        }

    }
    
    /**
     * input @
     * @param username
     */
    protected void inputAtUsername(String username, boolean autoAddAtSymbol){
        if(EMClient.getInstance().getCurrentUser().equals(username) ||
                chatType != EaseConstant.CHATTYPE_GROUP){
            return;
        }
        EaseAtMessageHelper.get().addAtUser(username);
        EaseUser user = EaseUserUtils.getUserInfo(username);
        if (user != null){
            username = user.getNick();
        }
        if(autoAddAtSymbol)
            inputMenu.insertText("@" + username + " ");
        else
            inputMenu.insertText(username + " ");
    }
    
    
    /**
     * input @
     * @param username
     */
    protected void inputAtUsername(String username){
        inputAtUsername(username, true);
    }
    

    //send message
    protected void sendTextMessage(String content) {
        if(EaseAtMessageHelper.get().containsAtUsername(content)){
            sendAtMessage(content);
        }else{
            //TODO:在这里将发送的消息进行加密（使用DES加密）
            if (saveOtherPublicKeyPath != null) {
                byte[] bytes = CryptUtil.desEncrypt(content.getBytes(), CryptUtil.pass.getBytes());
                final String s = Base64.encodeToString(bytes, Base64.NO_WRAP);
                final EMMessage message = EMMessage.createTxtSendMessage(s, toChatUsername);
                final ChatType type = message.getChatType();
                final EMMessage.Direct direct = message.direct();
                //TODO:上传文本聊天信息到服务器的数据库中
                new Thread(new Runnable() {
                    @Override
                    public void run() {
                        ChatMessageBase chatTextMessage = new ChatMessageBase();
                        if (type == ChatType.Chat){
                            chatTextMessage.setChatType(0);
                        } else if (type == ChatType.GroupChat){
                            chatTextMessage.setChatType(1);
                        }
                        if (direct == EMMessage.Direct.RECEIVE){
                            chatTextMessage.setSendOrReceive(0);
                        }else {
                            chatTextMessage.setSendOrReceive(1);
                        }
                        chatTextMessage.setContent(s);
                        chatTextMessage.setFrom(message.getFrom());
                        chatTextMessage.setTo(message.getTo());
                        chatTextMessage.setTime(message.getMsgTime());
                        chatTextMessage.setTheType(0);
                        chatTextMessage.setId(UUID.randomUUID().toString());
                        ChatMessageUpLoad.chatMessageUpLoad(chatTextMessage, EaseChatFragment.this);
                    }
                }).start();
                sendMessage(message);
            }
        }
    }
    
    /**
     * send @ message, only support group chat message
     * @param content
     */
    @SuppressWarnings("ConstantConditions")
    private void sendAtMessage(String content){
        if(chatType != EaseConstant.CHATTYPE_GROUP){
            EMLog.e(TAG, "only support group chat message");
            return;
        }
        EMMessage message = EMMessage.createTxtSendMessage(content, toChatUsername);
        EMGroup group = EMClient.getInstance().groupManager().getGroup(toChatUsername);
        if(EMClient.getInstance().getCurrentUser().equals(group.getOwner()) && EaseAtMessageHelper.get().containsAtAll(content)){
            message.setAttribute(EaseConstant.MESSAGE_ATTR_AT_MSG, EaseConstant.MESSAGE_ATTR_VALUE_AT_MSG_ALL);
        }else {
            message.setAttribute(EaseConstant.MESSAGE_ATTR_AT_MSG,
                    EaseAtMessageHelper.get().atListToJsonArray(EaseAtMessageHelper.get().getAtMessageUsernames(content)));
        }
        sendMessage(message);
        
    }
    
    
    protected void sendBigExpressionMessage(String name, String identityCode){
        EMMessage message = EaseCommonUtils.createExpressionMessage(toChatUsername, name, identityCode);
        sendMessage(message);
    }

    protected void sendVoiceMessage(final String filePath, final int length) {
        final EMMessage message = EMMessage.createVoiceSendMessage(filePath, length, toChatUsername);
        File voiceFile = new File(filePath);
        //首先将语音信息文件上传到服务器中
        FileUpLoad.getFilePath(voiceFile, new IFileUpLoadUserDown() {
            @Override
            public void upLoadSuccess(final String fileUrl) {
                final ChatType type = message.getChatType();
                final EMMessage.Direct direct = message.direct();
                //TODO:上传语音聊天信息到服务器的数据库中
                new Thread(new Runnable() {
                    @Override
                    public void run() {
                        ChatMessageBase chatVoiceMessage = new ChatMessageBase();
                        if (type == ChatType.Chat){
                            chatVoiceMessage.setChatType(0);
                        } else if (type == ChatType.GroupChat){
                            chatVoiceMessage.setChatType(1);
                        }
                        if (direct == EMMessage.Direct.RECEIVE){
                            chatVoiceMessage.setSendOrReceive(0);
                        }else {
                            chatVoiceMessage.setSendOrReceive(1);
                        }
                        chatVoiceMessage.setFrom(message.getFrom());
                        chatVoiceMessage.setTo(message.getTo());
                        chatVoiceMessage.setTime(message.getMsgTime());
                        chatVoiceMessage.setFilePath(fileUrl);
                        chatVoiceMessage.setTimeLength(length);
                        chatVoiceMessage.setTheType(2);
                        chatVoiceMessage.setId(UUID.randomUUID().toString());
                        ChatMessageUpLoad.chatMessageUpLoad(chatVoiceMessage, EaseChatFragment.this);
                    }
                }).start();
            }

            @Override
            public void upLoadFail(BmobException exception) {

            }
        });
        sendMessage(message);
    }

    protected void sendImageMessage(final String imagePath) {
        final EMMessage message = EMMessage.createImageSendMessage(imagePath, false, toChatUsername);
        File imageFile = new File(imagePath);
        //首先将图片信息文件上传到服务器中
        FileUpLoad.getFilePath(imageFile, new IFileUpLoadUserDown() {
            @Override
            public void upLoadSuccess(final String fileUrl) {
                final ChatType type = message.getChatType();
                final EMMessage.Direct direct = message.direct();
                //TODO:上传图片聊天信息到服务器的数据库中
                new Thread(new Runnable() {
                    @Override
                    public void run() {
                        ChatMessageBase chatImageMessage = new ChatMessageBase();
                        if (type == ChatType.Chat){
                            chatImageMessage.setChatType(0);
                        } else if (type == ChatType.GroupChat){
                            chatImageMessage.setChatType(1);
                        }
                        if (direct == EMMessage.Direct.RECEIVE){
                            chatImageMessage.setSendOrReceive(0);
                        }else {
                            chatImageMessage.setSendOrReceive(1);
                        }
                        chatImageMessage.setFrom(message.getFrom());
                        chatImageMessage.setTo(message.getTo());
                        chatImageMessage.setTime(message.getMsgTime());
                        chatImageMessage.setTheType(1);
                        chatImageMessage.setSendOriginalImage(false); //默认不发送原图
                        chatImageMessage.setFilePath(fileUrl);
                        chatImageMessage.setId(UUID.randomUUID().toString());
                        ChatMessageUpLoad.chatMessageUpLoad(chatImageMessage, EaseChatFragment.this);
                    }
                }).start();
            }

            @Override
            public void upLoadFail(BmobException exception) {

            }
        });
        sendMessage(message);
    }

    protected void sendLocationMessage(final double latitude, final double longitude, final String locationAddress) {
        final EMMessage message = EMMessage.createLocationSendMessage(latitude, longitude, locationAddress, toChatUsername);
        final ChatType type = message.getChatType();
        final EMMessage.Direct direct = message.direct();
        //TODO:上传位置聊天信息到服务器的数据库中
        new Thread(new Runnable() {
            @Override
            public void run() {
                ChatMessageBase chatLocationMessage = new ChatMessageBase();
                if (type == ChatType.Chat){
                    chatLocationMessage.setChatType(0);
                } else if (type == ChatType.GroupChat){
                    chatLocationMessage.setChatType(1);
                }
                if (direct == EMMessage.Direct.RECEIVE){
                    chatLocationMessage.setSendOrReceive(0);
                }else {
                    chatLocationMessage.setSendOrReceive(1);
                }
                chatLocationMessage.setFrom(message.getFrom());
                chatLocationMessage.setTo(message.getTo());
                chatLocationMessage.setTime(message.getMsgTime());
                chatLocationMessage.setLatitude(latitude);
                chatLocationMessage.setLongitude(longitude);
                chatLocationMessage.setLocationAddress(locationAddress);
                chatLocationMessage.setTheType(3);
                chatLocationMessage.setId(UUID.randomUUID().toString());
                ChatMessageUpLoad.chatMessageUpLoad(chatLocationMessage, EaseChatFragment.this);
            }
        }).start();
        sendMessage(message);
    }

    protected void sendVideoMessage(String videoPath, String thumbPath, int videoLength) {
        EMMessage message = EMMessage.createVideoSendMessage(videoPath, thumbPath, videoLength, toChatUsername);
        sendMessage(message);
    }

    protected void sendFileMessage(String filePath) {
        EMMessage message = EMMessage.createFileSendMessage(filePath, toChatUsername);
        sendMessage(message);
    }
    
    
    protected void sendMessage(final EMMessage message){
        if (message == null) {
            return;
        }
        if(chatFragmentHelper != null){
            //set extension
            chatFragmentHelper.onSetMessageAttributes(message);
        }
        if (chatType == EaseConstant.CHATTYPE_GROUP){
            message.setChatType(ChatType.GroupChat);
        }else if(chatType == EaseConstant.CHATTYPE_CHATROOM){
            message.setChatType(ChatType.ChatRoom);
        }
        //send message
        EMClient.getInstance().chatManager().sendMessage(message);
        //refresh ui
        if(isMessageListInited) {
            messageList.refreshSelectLast();
        }
    }
    
    
    public void resendMessage(EMMessage message){
        message.setStatus(EMMessage.Status.CREATE);
        EMClient.getInstance().chatManager().sendMessage(message);
        messageList.refresh();
    }
    
    //===================================================================================
    

    /**
     * send image
     * 
     * @param selectedImage
     */
    protected void sendPicByUri(Uri selectedImage) {
        String[] filePathColumn = { MediaStore.Images.Media.DATA };
        Cursor cursor = getActivity().getContentResolver().query(selectedImage, filePathColumn, null, null, null);
        if (cursor != null) {
            cursor.moveToFirst();
            int columnIndex = cursor.getColumnIndex(filePathColumn[0]);
            String picturePath = cursor.getString(columnIndex);
            cursor.close();
            cursor = null;

            if (picturePath == null || picturePath.equals("null")) {
                Toast toast = Toast.makeText(getActivity(), R.string.cant_find_pictures, Toast.LENGTH_SHORT);
                toast.setGravity(Gravity.CENTER, 0, 0);
                toast.show();
                return;
            }
            sendImageMessage(picturePath);
        } else {
            File file = new File(selectedImage.getPath());
            if (!file.exists()) {
                Toast toast = Toast.makeText(getActivity(), R.string.cant_find_pictures, Toast.LENGTH_SHORT);
                toast.setGravity(Gravity.CENTER, 0, 0);
                toast.show();
                return;

            }
            sendImageMessage(file.getAbsolutePath());
        }

    }
    
    /**
     * send file
     * @param uri
     */
    protected void sendFileByUri(Uri uri){
        String filePath = null;
        if ("content".equalsIgnoreCase(uri.getScheme())) {
            String[] filePathColumn = { MediaStore.Images.Media.DATA };
            Cursor cursor = null;

            try {
                cursor = getActivity().getContentResolver().query(uri, filePathColumn, null, null, null);
                int column_index = cursor.getColumnIndexOrThrow("_data");
                if (cursor.moveToFirst()) {
                    filePath = cursor.getString(column_index);
                }
            } catch (Exception e) {
                e.printStackTrace();
            } finally {
                if (cursor != null) {
                    cursor.close();
                }
            }
        } else if ("file".equalsIgnoreCase(uri.getScheme())) {
            filePath = uri.getPath();
        }
        if (filePath == null) {
            return;
        }
        File file = new File(filePath);
        if (!file.exists()) {
            Toast.makeText(getActivity(), R.string.File_does_not_exist, Toast.LENGTH_SHORT).show();
            return;
        }
        //limit the size < 10M
        if (file.length() > 10 * 1024 * 1024) {
            Toast.makeText(getActivity(), R.string.The_file_is_not_greater_than_10_m, Toast.LENGTH_SHORT).show();
            return;
        }
        sendFileMessage(filePath);
    }

    /**
     * capture new image
     */
    protected void selectPicFromCamera() {
        if (!EaseCommonUtils.isSdcardExist()) {
            Toast.makeText(getActivity(), R.string.sd_card_does_not_exist, Toast.LENGTH_SHORT).show();
            return;
        }

        cameraFile = new File(PathUtil.getInstance().getImagePath(), EMClient.getInstance().getCurrentUser()
                + System.currentTimeMillis() + ".jpg");
        //noinspection ResultOfMethodCallIgnored
        cameraFile.getParentFile().mkdirs();
        startActivityForResult(
                new Intent(MediaStore.ACTION_IMAGE_CAPTURE).putExtra(MediaStore.EXTRA_OUTPUT, Uri.fromFile(cameraFile)),
                REQUEST_CODE_CAMERA);
    }

    /**
     * select local image
     */
    protected void selectPicFromLocal() {
        Intent intent;
        if (Build.VERSION.SDK_INT < 19) {
            intent = new Intent(Intent.ACTION_GET_CONTENT);
            intent.setType("image/*");

        } else {
            intent = new Intent(Intent.ACTION_PICK, android.provider.MediaStore.Images.Media.EXTERNAL_CONTENT_URI);
        }
        startActivityForResult(intent, REQUEST_CODE_LOCAL);
    }



    /**
     * clear the conversation history
     * 
     */
    protected void emptyHistory() {
        String msg = getResources().getString(R.string.Whether_to_empty_all_chats);
        new EaseAlertDialog(getActivity(),null, msg, null,new AlertDialogUser() {
            
            @Override
            public void onResult(boolean confirmed, Bundle bundle) {
                if(confirmed){
                    if (conversation != null) {
                        conversation.clearAllMessages();
                    }
                    messageList.refresh();
                }
            }
        }, true).show();
    }

    /**
     * open group detail
     * 
     */
    protected void toGroupDetails() {
        if (chatType == EaseConstant.CHATTYPE_GROUP) {
            EMGroup group = EMClient.getInstance().groupManager().getGroup(toChatUsername);
            if (group == null) {
                Toast.makeText(getActivity(), R.string.gorup_not_found, Toast.LENGTH_SHORT).show();
                return;
            }
            if(chatFragmentHelper != null){
                chatFragmentHelper.onEnterToChatDetails();
            }
        }else if(chatType == EaseConstant.CHATTYPE_CHATROOM){
        	if(chatFragmentHelper != null){
        	    chatFragmentHelper.onEnterToChatDetails();
        	}
        }
    }

    /**
     * hide
     */
    protected void hideKeyboard() {
        if (getActivity().getWindow().getAttributes().softInputMode != WindowManager.LayoutParams.SOFT_INPUT_STATE_HIDDEN) {
            if (getActivity().getCurrentFocus() != null)
                inputManager.hideSoftInputFromWindow(getActivity().getCurrentFocus().getWindowToken(),
                        InputMethodManager.HIDE_NOT_ALWAYS);
        }
    }
    
    /**
     * forward message
     * 
     * @param forward_msg_id
     */
    protected void forwardMessage(String forward_msg_id) {
        final EMMessage forward_msg = EMClient.getInstance().chatManager().getMessage(forward_msg_id);
        EMMessage.Type type = forward_msg.getType();
        switch (type) {
        case TXT:
            if(forward_msg.getBooleanAttribute(EaseConstant.MESSAGE_ATTR_IS_BIG_EXPRESSION, false)){
                sendBigExpressionMessage(((EMTextMessageBody) forward_msg.getBody()).getMessage(),
                        forward_msg.getStringAttribute(EaseConstant.MESSAGE_ATTR_EXPRESSION_ID, null));
            }else{
                // get the content and send it
                String content = ((EMTextMessageBody) forward_msg.getBody()).getMessage();
                sendTextMessage(content);
            }
            break;
        case IMAGE:
            // send image
            String filePath = ((EMImageMessageBody) forward_msg.getBody()).getLocalUrl();
            if (filePath != null) {
                File file = new File(filePath);
                if (!file.exists()) {
                    // send thumb nail if original image does not exist
                    filePath = ((EMImageMessageBody) forward_msg.getBody()).thumbnailLocalPath();
                }
                sendImageMessage(filePath);
            }
            break;
        default:
            break;
        }
        
        if(forward_msg.getChatType() == EMMessage.ChatType.ChatRoom){
            EMClient.getInstance().chatroomManager().leaveChatRoom(forward_msg.getTo());
        }
    }

    /**
     * listen the group event
     * 
     */
    class GroupListener extends EaseGroupListener {

        @Override
        public void onUserRemoved(final String groupId, String groupName) {
            getActivity().runOnUiThread(new Runnable() {

                public void run() {
                    if (toChatUsername.equals(groupId)) {
                        Toast.makeText(getActivity(), R.string.you_are_group, Toast.LENGTH_LONG).show();
                        Activity activity = getActivity();
                        if (activity != null && !activity.isFinishing()) {
                            activity.finish();
                        }
                    }
                }
            });
        }

        @Override
        public void onGroupDestroyed(final String groupId, String groupName) {
        	// prompt group is dismissed and finish this activity
            getActivity().runOnUiThread(new Runnable() {
                public void run() {
                    if (toChatUsername.equals(groupId)) {
                        Toast.makeText(getActivity(), R.string.the_current_group_destroyed, Toast.LENGTH_LONG).show();
                        Activity activity = getActivity();
                        if (activity != null && !activity.isFinishing()) {
                            activity.finish();
                        }
                    }
                }
            });
        }
    }

    /**
     * listen chat room event
     */
    class ChatRoomListener extends EaseChatRoomListener {

        @Override
        public void onChatRoomDestroyed(final String roomId, final String roomName) {
            getActivity().runOnUiThread(new Runnable() {
                public void run() {
                    if (roomId.equals(toChatUsername)) {
                        Toast.makeText(getActivity(), R.string.the_current_chat_room_destroyed, Toast.LENGTH_LONG).show();
                        Activity activity = getActivity();
                        if (activity != null && !activity.isFinishing()) {
                            activity.finish();
                        }
                    }
                }
            });
        }

        @Override
        public void onRemovedFromChatRoom(final String roomId, final String roomName, final String participant) {
            getActivity().runOnUiThread(new Runnable() {
                public void run() {
                    if (roomId.equals(toChatUsername)) {
                        Toast.makeText(getActivity(), R.string.quiting_the_chat_room, Toast.LENGTH_LONG).show();
                        Activity activity = getActivity();
                        if (activity != null && !activity.isFinishing()) {
                            activity.finish();
                        }
                    }
                }
            });
        }

        @Override
        public void onMemberJoined(final String roomId, final String participant) {
            if (roomId.equals(toChatUsername)) {
                getActivity().runOnUiThread(new Runnable() {
                    public void run() {
                        Toast.makeText(getActivity(), "member join:" + participant, Toast.LENGTH_LONG).show();
                    }
                });
            }
        }

        @Override
        public void onMemberExited(final String roomId, final String roomName, final String participant) {
            if (roomId.equals(toChatUsername)) {
                getActivity().runOnUiThread(new Runnable() {
                    public void run() {
                        Toast.makeText(getActivity(), "member exit:" + participant, Toast.LENGTH_LONG).show();
                    }
                });
            }
        }


    }

    protected EaseChatFragmentHelper chatFragmentHelper;
    public void setChatFragmentListener(EaseChatFragmentHelper chatFragmentHelper){
        this.chatFragmentHelper = chatFragmentHelper;
    }
    
    public interface EaseChatFragmentHelper{
        /**
         * set message attribute
         */
        void onSetMessageAttributes(EMMessage message);

        /**
         * enter to chat detail
         */
        void onEnterToChatDetails();
        
        /**
         * on avatar clicked
         * @param username
         */
        void onAvatarClick(String username);
        
        /**
         * on avatar long pressed
         * @param username
         */
        void onAvatarLongClick(String username);
        
        /**
         * on message bubble clicked
         */
        boolean onMessageBubbleClick(EMMessage message);
        
        /**
         * on message bubble long pressed
         */
        void onMessageBubbleLongClick(EMMessage message);
        
        /**
         * on extend menu item clicked, return true if you want to override
         * @param view 
         * @param itemId 
         * @return
         */
        boolean onExtendMenuItemClick(int itemId, View view);
        
        /**
         * on set custom chat row provider
         * @return
         */
        EaseCustomChatRowProvider onSetCustomChatRowProvider();
    }
    
}
